<style scoped>
.formIn {
  width: 190px;
}

.el-main {
  padding: 0;
}
</style>

<template>
  <el-container style="height: 100%; width: 100%">
    <!--部门树状图-->
    <el-aside width="15%">
      <el-input placeholder="输入部门名" v-model="deptText" clearable prefix-icon="el-icon-search" size="small"
                style="width: 100%"/>
      <el-tree
          ref="tree"
          :data="deptTree"
          :props="{ label: 'name', children: 'childDept' }"
          :filter-node-method="deptNode"
          node-key="deptId"
          @node-click="userByDept"/>
    </el-aside>

    <el-main>
      <!--搜索-->
      <el-form ref="form" v-if="searchBox" :model="search" inline style="width: 100%;">
        <el-form-item>
          <span>用户名：</span>
          <el-input v-model="search.userName" placeholder="请输入用户名" clearable size="mini" class="formIn"/>
        </el-form-item>
        <el-form-item>
          <span>手机号：</span>
          <el-input v-model="search.phonenumber" placeholder="请输入手机号" clearable size="mini" class="formIn"/>
        </el-form-item>
        <el-form-item label="状态：">
          <el-select v-model="search.status" placeholder="请选择状态" clearable size="mini" class="formIn">
            <el-option v-for="sta in statuss" :label="sta.dictLabel" :value="sta.dictValue"/>
          </el-select>
        </el-form-item>
        <el-form-item>
          <span>创建时间：</span>
          <el-date-picker
              size="mini"
              v-model="search.createTime"
              type="daterange"
              range-separator="至"
              start-placeholder="开始日期"
              end-placeholder="结束日期"
              value-format="yyyy-MM-dd"
              class="formIn"/>
        </el-form-item>
        <el-form-item>
          <el-button type="success" size="mini" @click="allPage(1)">
            <i class="el-icon-search"/>搜索
          </el-button>
          <el-button size="mini" @click="nullSearch">
            <i class="el-icon-refresh"/>重置
          </el-button>
        </el-form-item>
      </el-form>

      <!--添加+批量操作-->
      <div>
        <el-button type="primary" size="small" @click="addPage">
          <i class="el-icon-plus"/>添加
        </el-button>
        <el-button type="success" size="small" disabled>
          <i class="el-icon-edit"/>修改
        </el-button>
        <el-button type="danger" size="small" @click="batchUser" :disabled="batch">
          <i class="el-icon-delete"/>删除
        </el-button>
        <el-button size="small" type="primary" @click="dialogImport = true">导入</el-button>
        <el-button type="warning" size="small" @click="exports" :disabled="ex">
          <i class="el-icon-download"/>导出选择
        </el-button>
        <el-button type="warning" @click="exports(1)" size="small">
          <i class="el-icon-download"/>导出所有
        </el-button>
      </div>

      <!--文件上传-->
      <el-dialog :visible.sync="dialogImport" width="400px">
        <el-upload
            ref="eImport"
            drag
            action="/sysUser/import"
            :http-request="eImport"
            :auto-upload="false">
          <i class="el-icon-upload"></i>
          <div class="el-upload__text">将文件拖到此处，或<em>点击上传</em></div>
          <div class="el-upload__tip" slot="tip">提示：仅允许导入“xls”或“xlsx”格式文件！</div>
        </el-upload>
        <p/>
        <div>
          <el-button @click="dialogImport = false" size="small">取消</el-button>
          <el-button type="primary" @click="eImportButton" size="small">确定</el-button>
        </div>
      </el-dialog>

      <!--表格-->
      <el-table :data="users"
                @select="selectId" @select-all="selectAllId"
                :cell-style="{'text-align':'center'}"
                :header-cell-style="{background:'#E4E7ED','text-align':'center',color:'#000'}"
                max-height="100%" style="width: 100%;">
        <el-table-column type="selection"
                         header-align="center"
                         align="center"/>
        <el-table-column prop="userId" label="编号"/>
        <el-table-column prop="userName" label="账户"/>
        <el-table-column prop="nickName" label="昵称"/>
        <el-table-column label="部门">
          <template slot-scope="dept">
            <p v-text="dept.row.dept.deptName"></p>
          </template>
        </el-table-column>
        <el-table-column prop="phonenumber" label="手机号"/>
        <el-table-column label="状态" width="60px">
          <template slot-scope="status">
            <el-switch
                v-model="status.row.status"
                active-color="#13ce66" inactive-color="#bababa"
                active-value="0" inactive-value="1"
                @change="updateStatus(status.row)"/>
          </template>
        </el-table-column>
        <el-table-column prop="createTime" label="创建时间" width="160px"/>
        <el-table-column label="操作" width="160px">
          <template slot-scope="scope">
            <el-button type="text" @click="updatePage(scope.row)" size="mini">修改</el-button>
            <el-button type="text" v-if="scope.row.userId !== 1" @click="remove(scope.row)" size="mini">删除</el-button>
            <el-button type="text" @click="reset(scope.row)" size="mini">重置</el-button>
          </template>
        </el-table-column>
      </el-table>

      <!--分页-->
      <el-pagination
          background
          :total="total"
          @size-change="sizeTo" @current-change="allPage"
          layout="sizes, prev, pager, next, jumper, total"
          :page-sizes="[10, 20, 30, 50]"
          style="float: right"/>
      <div style="clear: both"/><!--清除浮动-->
    </el-main>

    <!--添加修改表单-->
    <el-dialog ref="addUpForm" :visible.sync="dialogSaveUpdate" :title="saveUpdateName" width="60%">
      <el-form ref="addUpForm" :model="user" :rules="saveUpdateRules" inline>
        <el-form-item prop="userName" label="用户名：">
          <el-input v-model="user.userName" placeholder="输入用户名" clearable class="formIn"/>
        </el-form-item>
        <el-form-item prop="nickName" label="昵称：">
          <el-input v-model="user.nickName" placeholder="输入昵称" clearable class="formIn"/>
        </el-form-item>
        <el-form-item v-if="saveUpdateName === '添加'" prop="password" label="密码：">
          <el-input v-model="user.password" placeholder="输入密码" clearable class="formIn"/>
        </el-form-item>
        <el-form-item label="部门：" prop="deptId">
          <Treeselect placeholder="选择部门"
                      v-model="user.deptId"
                      :options="deptTree"
                      key="id"
                      :normalizer="normalizer"
                      :multiple="false"
                      style="width: 200px"/>
        </el-form-item>
        <el-form-item label="手机号：" prop="phonenumber">
          <el-input v-model="user.phonenumber" placeholder="输入手机号" clearable class="formIn"/>
        </el-form-item>
        <el-form-item label="邮箱：" prop="email">
          <el-input
              v-model="user.email"
              validate-event
              placeholder="输入邮箱"
              clearable
              class="formIn"/>
        </el-form-item>
        <el-form-item label="用户性别：">
          <el-select
              v-model="user.sex"
              placeholder="请选择性别"
              class="formIn">
            <el-option v-for="(sex,index) in sexs"
                       :key="index" :label="sex.dictLabel" :value="sex.dictValue"/>
          </el-select>
        </el-form-item>
        <el-form-item label="状态">
          <el-radio-group v-model="user.status" class="formIn">
            <el-radio :label="0">正常</el-radio>
            <el-radio :label="1">禁用</el-radio>
          </el-radio-group>
        </el-form-item>
        <el-form-item label="岗位">
          <el-select v-model="user.postIds" multiple>
            <el-option v-for="post in posts"
                       :key="post.postId" :label="post.postName" :value="post.postId"/>
          </el-select>
        </el-form-item>
        <el-form-item label="角色">
          <el-select v-model="user.roleIds" multiple>
            <el-option v-for="role in roles"
                       :key="role.roleId" :label="role.roleName" :value="role.roleId"/>
          </el-select>
        </el-form-item>
        <el-form-item label="备注">
          <el-input v-model="user.remark" type="textarea"
                    placeholder="备注" clearable
                    rows="2" class="formIn"/>
        </el-form-item>

        <div style="position: absolute; bottom: 20px; right: 20px;">
          <el-button @click="dialogSaveUpdate = false" size="small">取消</el-button>
          <el-button type="primary" @click="submitForm(user)" size="small">确定</el-button>
        </div>
      </el-form>
    </el-dialog>
  </el-container>
</template>

<script>
import Treeselect from '@riophae/vue-treeselect'
import {saveAs} from "file-saver";
import '@riophae/vue-treeselect/dist/vue-treeselect.css'

export default {
  components: {Treeselect},

  watch: {
    deptText(val) {
      this.$refs.tree.filter(val);
    }
  },

  methods: {
    //导入确定按钮
    eImportButton() {
      this.$refs.eImport.submit();
    },
    //导入请求
    eImport(params) {
      const file = params.file;
      const formData = new FormData();
      formData.append('userEx', file);
      this.$axios.post('/sysUser/import', formData, {
        headers: {'Content-Type': 'multipart/form-data'}
      }).then(res => {
        this.dialogImport = false;
        this.$message.success("导入成功");
        setTimeout(function () {
          location.reload();
        }, 500);
      }).catch(error => {
        this.$message.error("导入失败");
      });
    },
    //导出 1:导出所有
    exports(sta) {
      this.$prompt('输入文件名', '导出', {
        confirmButtonText: '确定', cancelButtonText: '取消',
      }).then(({value}) => {
        let userIds;
        if (sta === 1) {
          userIds = '';
        } else {
          userIds = this.selectList;
        }
        this.$axios.get("/sysUser/export?strIds=" + userIds, {responseType: 'arraybuffer'}).then(res => {
          const blob = new Blob([res.data], {type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'});
          saveAs(blob, value + '.xlsx');
        });
      });
    },

    //删除用户
    remove(user) {
      this.$confirm("确定删除用户？", "警告", {
        confirmButtonText: "确定",
        cancelButtonText: "取消",
        type: 'error'
      }).then(() => {
        user.delFlag = "2";
        this.saveUpdate(user, "删除成功");
        location.reload();
      }).catch(() => {
      });
    },
    //批量删除
    batchUser() {
      this.$confirm("确定删除用户？", "警告", {
        confirmButtonText: "确定",
        cancelButtonText: "取消",
        type: 'error'
      }).then(() => {
        const userIds = this.selectList
        this.$axios.delete('/sysUser/user', {
          data: {userIds},
          headers: {'Content-Type': 'application/json'}
        }).then(res => {
          if (res.data.code === 200) {
            this.$message.success("删除成功！");
            location.reload();
          }
        });
      }).catch(() => {
      });
    },
    //更改账户状态
    updateStatus(user) {
      //停用
      if (user.status === "1") {
        this.$confirm("是否停用账户？", "提示", {
          confirmButtonText: "确定",
          cancelButtonText: "取消",
          type: 'warning'
        }).then((() => {
          this.saveUpdate(user, "已停用")
        })).catch(() => {
          user.status = "0";
        });
      }
      //启用
      else {
        this.saveUpdate(user, "已启用")
      }
    },
    //重置账户
    reset(user) {
      this.$prompt('请输入新密码', '重置', {
        confirmButtonText: '确定',
        cancelButtonText: '取消',
      }).then(({value}) => {
        user.password = value;
        this.$axios.put('/sysUser/userpwd', user).then(res => {
          if (res.data.code === 200) {
            this.$message.success('新密码是: ' + value);
          }
        });
      });
    },
    //添加和修改账户
    saveUpdate(thisUser, msg) {
      console.log(thisUser)
      const user = JSON.parse(JSON.stringify(thisUser))
      //添加
      if (user.userId === 0) {
        console.log("添加")
        user.createBy = localStorage.getItem("username");
        this.$axios.post('/sysUser/user', user).then(res => {
          if (res.data.code === 200) {
            this.$message.success("添加成功");
            this.dialogSaveUpdate = false;
            this.allPage(1);
          } else if (res.data.code === 400) {
            this.$message.error("用户为空");
          }
        });
      }
      //修改
      else {
        console.log("修改")
        user.updateBy = localStorage.getItem("username");
        this.$axios.put("/sysUser/user", user).then(res => {
          if (res.data.code === 200) {
            if (!msg) {
              this.$message.success("修改完成");
            } else {
              this.$message.success(msg);
            }
          } else {
            this.$message.error("服务器异常");
          }
        });
        this.dialogSaveUpdate = false;
      }
    },
    //提交表单验证
    submitForm(user) {
      if (this.$refs.addUpForm && this.$refs.addUpForm.validate) {
        // 如果判断存在且需要验证，则执行验证
        this.$refs.addUpForm.validate(valid => {
          if (valid) {
            // 验证通过，执行提交操作
            this.saveUpdate(user);
          }
        });
      } else {
        // 如果判断不存在或不需要验证，直接执行提交操作
        this.saveUpdate(user);
      }
    },

    //树节点点击筛选用户
    userByDept(data) {
      if (data.childDept.length > 0) {
        this.search.deptIds = this.getDeptIds(data);
        this.search.deptIds.push(data.id);
      } else {
        this.search.deptIds = [];
        this.search.deptIds.push(data.id);
      }
      this.allPage(1)
    },
    //部门树节点筛选借调方法
    deptNode(value, data) {
      if (!this.deptText) return true;
      return data.name.includes(this.deptText);
    },

    //更改每页条数
    sizeTo(size) {
      this.sizes = size;
      this.allPage(1);
    },
    //重置搜索
    nullSearch() {
      this.search.userName = "";
      this.search = {
        userName: "",
        createTime: [],
        phonenumber: "",
        status: ""
      }
      this.allPage(1);
    },
    //分页数据+查询
    allPage(current) {
      // this.current = current;
      let staterTime = null;
      let endTime = null;
      if (this.search.createTime !== []) {
        staterTime = new Date(this.search.createTime[0]);
        endTime = new Date(this.search.createTime[1] + "T23:59:59");
      }
      this.$axios.post("/sysUser/user/" + current,
          {
            size: this.sizes,
            userName: this.search.userName,
            status: this.search.status,
            phonenumber: this.search.phonenumber,
            deptIds: this.search.deptIds,
            staterTime, endTime
          }).then(res => {
        if (res.data.code === 200) {
          this.users = res.data.data.records;
          this.total = res.data.data.total;
        }
      }).catch(res => {
        this.$message.error("连接异常")
      })
    },

    //显示修改表单+回填
    updatePage(user) {
      this.saveUpdateName = "修改";
      this.user = JSON.parse(JSON.stringify(user));
      if (user.status === '0') {
        this.user.status = 0;
      } else {
        this.user.status = 1;
      }
      this.dialogSaveUpdate = true;
      this.$refs.addUpForm.resetFields();
    },
    //显示添加表单+清空
    addPage() {
      this.user = {
        userId: 0,
        interactionId: 0,
        deptId: null,
        userName: "",
        nickName: '',
        userType: "",
        email: "",
        phonenumber: "",
        sex: "",
        avatar: "",
        password: "",
        status: 1,
        delFlag: 0,
        loginIp: "",
        loginDate: "",
        createBy: "",
        createTime: "",
        updateBy: "",
        updateTime: "",
        remark: "",
        roleId: [],
        postIds: [],
      };
      this.saveUpdateName = "添加";
      this.dialogSaveUpdate = true;
      if (this.$refs.addUpForm) {
        this.$refs.addUpForm.resetFields();
      }
    },

    //获取选择行的数据
    selectId(val) {
      this.selectList = [];
      for (let i = 0; i < val.length; i++) {
        this.selectList[i] = val[i].userId;
      }
      this.selectList.length > 0 ? this.batch = false : this.batch = true;
      this.selectList.length > 0 ? this.ex = false : this.ex = true;
    },
    //获取所有行数据
    selectAllId(val) {
      this.selectList = [];
      for (let i = 0; i < val.length; i++) {
        this.selectList[i] = val[i].userId;
      }
      this.selectList.length > 0 ? this.batch = false : this.batch = true;
      this.selectList.length > 0 ? this.ex = false : this.ex = true;
    },

    //部门树递归方法
    deptTreeDate(departments) {
      return departments.map(dept => ({
        id: dept.deptId,
        name: dept.deptName,
        childDept: dept.childDept ? this.deptTreeDate(dept.childDept) : [],
      }));
    },
    //获取子节点数组
    getDeptIds(data) {
      // 递归获取节点的下级节点的id数组
      const Ids = [];
      const traverse = (node) => {
        if (node.childDept && node.childDept.length > 0) {
          node.childDept.forEach(childNode => {
            Ids.push(childNode.id);
            traverse(childNode);
          });
        }
      };
      traverse(data);
      return Ids;
    },
    //转换添加修改部门下拉框数据结构
    normalizer(node) {
      // 去掉children=[]的children属性
      if (node.childDept && !node.childDept.length) {
        delete node.childDept
      }
      return {
        id: node.id,
        label: node.name,
        children: node.childDept
      }
    },
  },

  mounted() {
    //默认获取第1页
    this.allPage(1);
    //获取部门树
    this.$axios.get('/sysDept/deptTree').then(res => {
      if (res.data.code === 200) {
        this.deptTree = this.deptTreeDate(res.data.data);
      }
    });
    //获取性别数组
    this.$axios.get('/sysDictData-find?dictType=sys_user_sex').then(res => {
      this.sexs = res.data.data;
    });
    //获取岗位数组
    this.$axios.get('/sysPost/posts').then(res => {
      if (res.data.code === 200) {
        this.posts = res.data.data;
      }
    });
    //获取角色数组
    this.$axios.get('/sysRole/roles').then(res => {
      if (res.data.code === 200) {
        this.roles = res.data.data;
      }
    });
    //获取状态数组
    this.$axios.get('/sysDictData-find?dictType=sys_normal_disable').then(res => {
      this.statuss = res.data.data;
    });
  },

  data() {
    return {
      /*搜索框*/
      search: {
        deptIds: [],/*树节点部门id*/
        userName: "",/*用户名搜索框*/
        createTime: [],
        phonenumber: "",/*手机号搜索框*/
        status: "",/*状态搜索框*/
      },
      /*用户信息*/
      user: {
        userId: 0,
        deptId: 0,
        userName: "",
        nickName: "",
        userType: "",
        email: "",
        phonenumber: "",
        sex: "",
        avatar: "",
        password: "",
        status: '',
        delFlag: 0,
        loginIp: "",
        loginDate: "",
        createBy: "",
        createTime: "",
        updateBy: "",
        updateTime: "",
        remark: "",
        roleIds: [],
        postIds: [],
      },
      /*性别数组*/
      sexs: [],
      /*岗位数组*/
      posts: [],
      /*角色数组*/
      roles: [],
      users: [],/*分页用户数组*/
      total: 0,/*总条数*/
      sizes: 10,/*每页条数*/
      current: 1,
      dialogSaveUpdate: false,  /*添加修改表单状态*/
      dialogImport: false,      /*导入弹出框状态*/
      saveUpdateName: "",/*添加修改表单标题*/
      batch: true,/*批量删除按钮状态*/
      ex: true,/*导出按钮状态*/
      saveUpdateRules: {
        nickName: [{required: true, message: '请输入昵称', trigger: 'blur'}],
        userName: [{required: true, message: '请输入用户名', trigger: 'blur'}],
        password: [{required: true, message: '请输入密码', trigger: 'blur'}],
        phonenumber: [{required: true, message: '请输入手机号', trigger: 'blur'}],
        email: [
          {required: true, message: '请输入邮箱', trigger: 'blur'},
          {type: 'email', message: '邮箱格式不正确', trigger: 'blur'},
        ],
        deptId: [{required: true, message: '请输入手机号', trigger: 'blur'}],
      },/* 添加修改表单输入框规则 */
      deptText: "",
      deptTree: [],/*部门树数组*/
      statuss: [],/* 状态数组 */
      selectList: [],/*批量选择数组*/
      searchBox: true,
    }
  },

}
</script>
